﻿using System;
using System.Windows.Input;

namespace Demo04_BasicAnimation
{
	/// <summary>
	/// A class for handling events on UI elements
	/// </summary>
	public class InterfaceCommand : ICommand
	{
		#region Lifecycle
		/// <summary>
		/// Creates a command that will perform a given action when it is executed.
		/// </summary>
		/// <param name="execute">Action to perform.</param>
		/// <param name="canExecute">Function to validate execution ability.</param>
		public InterfaceCommand(Action execute, Func<bool> canExecute = null)
		{
			if (execute == null)
				throw new ArgumentNullException("execute");

			_execute = execute;
			_canExecute = canExecute;
		}
		#endregion

		#region Public Properties
		readonly Action _execute;
		readonly Func<bool> _canExecute;
		#endregion

		#region ICommand Members
		/// <summary>
		/// Event handler for when validation function changes.
		/// </summary>
		public event EventHandler CanExecuteChanged
		{
			add
			{
				if (_canExecute != null)
				{
					CommandManager.RequerySuggested += value;
				}
			}

			remove
			{
				if (_canExecute != null)
				{
					CommandManager.RequerySuggested -= value;
				}
			}
		}
		#endregion

		#region ICommand Methods
		/// <summary>
		/// Performs this command's action.
		/// </summary>
		/// <param name="parameter">(Unused)</param>
		public virtual void Execute(object parameter = null)
		{
			_execute();
		}

		/// <summary>
		/// Validates execution ability.
		/// </summary>
		/// <param name="parameter">(Unused)</param>
		/// <returns>Whether or not this command's action can be performed.</returns>
		public virtual bool CanExecute(object parameter = null)
		{
			return (_canExecute == null)
				? true
				: _canExecute();
		}
		#endregion
	}
}
